
/*
 * This is an implementation of the "middle c" sequence as described by
 * Gruenbaum and Shephard in "Tilings and Patterns" (isbn 0716711931 or 
 * 0486469816)
 *
 * A musical sequence is an aperiodic sequence of long and short intervals
 * that can be thought of as a one-dimensional aperiodic tiling
 */

var middle_c_data;
var middle_c_phi = (Math.sqrt(5) + 1) / 2;

function middle_c_get_distance(t) {
	var c = (middle_c_phi + 1) / 2;
	if (0 == t) { return 1 - c; }
	var m = ((t < 0) ? -1 : 1);
	var i = Math.abs(t) - 2;
	middle_c_get_term(i + 3);
	var d = c * m;
	if (i < 0) { return d; }
	d += m * (middle_c_data.S[i] + middle_c_data.L[i] * middle_c_phi);
	return d;
}

function middle_c_expand_sequence() {
	// l, s l, l s l, s l l s l,
	if (0 == middle_c_data.m.length) {
		middle_c_data.m = ['L', 'S', 'L'];
		middle_c_data.L = [1, 1, 2];
		middle_c_data.S = [0, 1, 1];
		middle_c_data.a = 0;
		middle_c_data.b = 1;
		return;
	}
	var b = middle_c_data.m.length;
	var i;
	var t;
	for (i = middle_c_data.a; i < b; ++i) {
		t = middle_c_data.m[i];
		middle_c_data.m.push(t);
		middle_c_data.L.push(middle_c_data.L[middle_c_data.L.length - 1]);
		middle_c_data.S.push(middle_c_data.S[middle_c_data.S.length - 1]);
		++middle_c_data[t][middle_c_data[t].length - 1];
	}
	middle_c_data.a = middle_c_data.b;
	middle_c_data.b = b;
}

function middle_c_get_term(n) {
	var t = n;
	if (0 == t) { return 'S'; }
	if (1 == t) { return 'L'; }
	if (t > 1) { t -= 2; }
	else { ++t; t *= -1; }
	if (null == middle_c_data) { middle_c_data = {
		m: [],
		L: [],
		S: [],
		a: 0,
		b: 0
	}}
	while (middle_c_data.m.length < t) {
		middle_c_expand_sequence();
	}
	return middle_c_data.m[t];
}
